package org.jetlinks.pro.clickhouse;

import org.hswebframework.ezorm.rdb.executor.wrapper.ResultWrapper;
import reactor.core.publisher.Flux;
import reactor.core.publisher.Mono;

import java.util.Map;

/**
 * ClickHouse 操作接口,用于执行CRUD等基本操作
 *
 * @author zhouhao
 * @since 1.9
 */
public interface ClickHouseOperations {

    /**
     * 获取数据库名
     *
     * @return 数据库名
     */
    String getDatabase();

    /**
     * 批量写入数据,规则:
     * <p>
     * 使用Flux中的第一条数据的{@link Map#keySet()}作为列,生成SQL:
     * <pre>
     *     insert into table (key1,key2,key3)values
     * </pre>
     * 后续的数据使用第一条数据的{@link Map#keySet()}来获取值并生成values.
     * <p>
     * ⚠️: values流不能耗时过久
     *
     * @param table  表
     * @param values 批量数据流
     * @return void
     */
    Mono<Void> insert(String table,
                      Flux<Map<String, Object>> values);

    /**
     * 写入数据,调用此方法不会立即写入,而是进行缓冲后批量写入
     *
     * @param table 表
     * @param value 值
     * @return void
     */
    Mono<Void> insert(String table, Map<String, Object> value);

    /**
     * 执行SQL,忽略成功返回结果,通常用于DDL操作
     *
     * @param sql SQL
     * @return void
     */
    Mono<Void> execute(String sql);

    /**
     * 执行查询操作,可通过在SQL中指定format来自定义返回数据格式,默认使用JSON.
     * 不同的format,解析的性能可能不同.
     *
     * @param sql SQL语句
     * @return 将查询的列转为Map流
     * @see DefaultFormat
     */
    <R> Flux<R> query(String sql, ResultWrapper<R, ?> wrapper);

}
